<?php

namespace App\Models;

use App\Services\WxMp\WxMpListService;
use Illuminate\Notifications\Notifiable;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Database\Eloquent\SoftDeletes;
use App\Notifications\ResetPassword as ResetPasswordNotification;

/**
 * 系统用户数据模型
 * @package App\Models
 */
class SysUser extends Authenticatable
{
    use Notifiable, SoftDeletes;

    /**
     * The attributes that are mass assignable.
     *
     * @var array
     */
    protected $fillable = [
        'name', 'email', 'password',
    ];

    /**
     * The attributes that should be hidden for arrays.
     *
     * @var array
     */
    protected $hidden = [
        'password', 'remember_token',
    ];
    /**
     * 应该被转换成原生类型的属性。
     * @var array
     */
    protected $casts = [
        'appid_choice' => 'array',
    ];
    /**
     * 重置密码重构
     * @param string $token
     */
    public function sendPasswordResetNotification($token)
    {
        $this->notify(new ResetPasswordNotification($token));
    }

    /**
     * 获取用户角色列表
     * @return \Illuminate\Database\Eloquent\Relations\BelongsToMany
     */
    public function roles()
    {
        return $this->belongsToMany('App\Models\SysRole','sys_role_users','user_id','role_id')->withTimestamps();
    }

    /**
     * 判断用户是否具有某个角色
     * @param $role 权限对应的角色列表
     * @return bool
     */
    public function hasRole($role)
    {
        if (is_string($role)){
            return $this->roles->contains('name', $role);
        }
        //过滤掉非当前用户选择的微信应用的权限
        $userAppid = !empty($this->appid_choice['appid']) ? $this->appid_choice['appid'] : '';
        if (!empty($userAppid)){
            foreach ($role as $k => $v){
                if ($v->pivot->appid != $userAppid){
                    $role->forget($k);
                }
            }
        }
        //判断拥有该权限的角色和当前用户的角色是否有重合存在交集。双感叹号相当于强制转换为布尔类型
        return !! $role->intersect($this->roles)->count();
    }

    /**
     * 判断用户是否具有某权限
     * @param $permission
     * @return bool
     */
    public function hasPermission($permission)
    {
        if ($permission->is_public == 1){//公共权限直接返回true
            return true;
        }else{
            //判断是否是超级管理员
            if ($this->hasRole('supper-admin')){
                return true;
            }else{
                return $this->hasRole($permission->roles);
            }
        }
    }

    /**
     * 给用户分配角色
     * @param $role
     * @return \Illuminate\Database\Eloquent\Model
     */
    public function assignRole($role)
    {
        return $this->roles()->save(
            SysRole::whereName($role)->firstOrFail()
        );
    }

    /**
     * 获取当前用户微信应用列表
     * @return array|bool
     */
    public function getWxMpList()
    {
        $userWxMpList = session('user_wxmp_list');
        if (!empty($userWxMpList)){
            return $userWxMpList;
        }
        $userWxMpList = [];
        //判断是否是超级管理员
        if ($this->hasRole('supper-admin')){
            $userWxMpList = (new WxMpListService())->getValidMpList();
        }else{
            $roleList = $this->roles;
            $appIds = [];
            foreach ($roleList as $role){
                if (!empty($role->appids)){
                    $appIds = array_merge($appIds, $role->appids);
                }
            }
            $appIds = array_unique($appIds);
            if (!empty($appIds)){
                $userWxMpList = (new WxMpListService())->getValidMyListByAppids($appIds);
            }
        }
        session(['user_wxmp_list'=>$userWxMpList]);
        return $userWxMpList;
    }

    /**
     * 设置当前已选微信应用
     * @param $appId
     * @throws \Exception
     */
    public function setWxMpCurrent($appId)
    {
        $wxMpData = (new WxMpListService())->getValidMpByAppid($appId);
        if (empty($wxMpData)){
            throw new \Exception('无效的微信应用');
        }
        $appidChoice = [
            'appid' => $wxMpData['appid'],
            'nick_name' => $wxMpData['nick_name'],
            'head_img' => $wxMpData['head_img'],
        ];
        session(['user_appid_choice'=>$appidChoice]);
    }
    /**
     * 获取当前微信应用
     * @return array|mixed
     */
    public function getWxMpCurrent()
    {
        $appidChoice = session('user_appid_choice');
        if (empty($appidChoice)){
            $wxMpList = $this->getWxMpList();
            if (!empty($wxMpList)){
                $wxMpCurrent = !empty($wxMpList[0]) ? $wxMpList[0] : [];
                $appidChoice = [
                    'appid' => $wxMpCurrent['appid'],
                    'nick_name' => $wxMpCurrent['nick_name'],
                    'head_img' => $wxMpCurrent['head_img'],
                ];
                session(['user_appid_choice'=>$appidChoice]);
            }
        }

        return $appidChoice;
    }

    /**
     * 获取当前用户的微信应用标识ID
     * @return mixed
     * @throws \Exception
     */
    public function getWxMpAppIdCurrent()
    {
        $appidChoice = session('user_appid_choice');
        if (empty($appidChoice['appid'])){
            throw new \Exception('微信应用标识为空');
        }
        return $appidChoice['appid'];
    }
}
